/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */

package gride.project;

import gride.exceptions.XMLFormatException;
import gride.groovy.Regex;
import java.io.File;
import java.io.IOException;
import javax.swing.JOptionPane;
import org.w3c.dom.Element;
import org.w3c.dom.NodeList;

/**
 *
 * @author lukasz
 */
public class GrideScript
{
    // <editor-fold defaultstate="expanded" desc="Members">

    /**
     * full name of the script (package + script name)
     */
    protected String fullName;
    /**
     * location of the source file
     */
    protected File sourceFile = null;
    /**
     * location of the class file
     */
    protected File classFile = null;
    /**
     * indicates whether the script has been modified since last save
     */
    protected boolean modified;
    /**
     * indicates whether this is a main script of a project
     */
    protected boolean mainScript;

    private boolean controlledPackage = true;
    
    // </editor-fold>
    
    
    // <editor-fold defaultstate="expanded" desc="Constructors">
    
    /**
     * Default constructor
     * @param fullName
     */
    public GrideScript(String fullName)
    {
        this.fullName = fullName;
        mainScript = false;
    }
    
    /**
     * constructor taking the package name and script name separately
     * @param name
     * @param pack
     */
    public GrideScript(String name, String pack)
    {
        this(((pack != null) && (!pack.equals("")) ? 
             pack + "." + name :
             name));
    }

    /**
     * loads a script from the given xml Element node
     * @param node
     * @return
     * @throws gride.exceptions.XMLFormatException
     */
    public static GrideScript loadScript(Element node) throws XMLFormatException
    {
        GrideScript script;

        try
        {
            script = new GrideScript(node.getAttribute("Name"));

            String mainString = node.getAttribute("Main");
            if (mainString != null && !mainString.equals(""))
                script.setMainScript(Boolean.parseBoolean(mainString));
            else
                script.setMainScript(false);

            NodeList nodes = node.getElementsByTagName("SourceFile");
            if (nodes.getLength() == 0)
                throw new XMLFormatException("Wrong format of project XML file");

            script.setSourceFile(new File(nodes.item(0).getTextContent()));

            nodes = node.getElementsByTagName("ClassFile");
            if (nodes.getLength() == 1)
                script.setClassFile(new File(nodes.item(0).getTextContent()));
        }
        catch (IOException e)
        {
            return null;
        }

        return script;
    }
    
    // </editor-fold>


    // <editor-fold defaultstate="expanded" desc="Getters/Setters">


    // </editor-fold>



    // <editor-fold defaultstate="expanded" desc="Public Methods">

    /**
     * gets the xml representing this script
     * @return
     */
    public String getXML()
    {
        StringBuilder xml = new StringBuilder();

        xml.append("<Script Name=\"" + fullName + "\" Main=\"" + mainScript +
                   "\">\n");
        xml.append("\t<SourceFile>" + sourceFile + "</SourceFile>\n");
        
        if (classFile != null)
            xml.append("\t<ClassFile>" + classFile + "</ClassFile>\n");
        
        xml.append("</Script>");

        return xml.toString();
    }

    /**
     * gets the full name of the script
     * @return
     */
    public String getFullName() {
        return fullName;
    }

    /**
     * sets the full name of the script
     * @param name
     */
    public void setFullName(String name)
    {
        fullName = name;
    }

    /**
     * gets the name of the script
     * @return
     */
    public String getName() {
        return Regex.extractClassName(fullName);
    }

    /**
     * gets the package of the script
     * @return
     */
    public String getPackage() {
        return Regex.extractPackageName(fullName);
    }

    /**
     * gets the source file of the script
     * @return
     */
    public File getSourcefile() {
        return sourceFile;
    }

    /**
     * sets the source file of the script
     * @param file
     * @throws java.io.IOException
     */
    public void setSourceFile(File file) throws IOException {
        this.sourceFile = file;
        if (sourceFile != null) {            
            sourceFile.getParentFile().mkdirs();
            sourceFile.createNewFile();
        }
    }

    /**
     * gets the class file of the script
     * @return
     */
    public File getClassFile()
    {
        return classFile;
    }

    /**
     * sets the class file of the script
     * @param file
     */
    public void setClassFile(File file)
    {
        this.classFile = file;

        if (file != null)
            file.getParentFile().mkdirs();
    }

    /**
     * gets the modification flag
     * @return
     */
    public boolean isModified()
    {
        return modified;
    }

    /**
     * sets the modification flag
     * @param value
     */
    public void setModified(boolean value)
    {
        this.modified = value;
    }

    /**
     * checks if this is a main script in a project
     * @return
     */
    public boolean isMainScript()
    {
        return mainScript;
    }

    /**
     * sets this script as main in a project
     * @param mainScript
     */
    public void setMainScript(boolean mainScript)
    {
        this.mainScript = mainScript;
    }

    /**
     * checks whether the package declaration of this script should be
     * controlled
     * @return
     */
    public boolean isControlledPackage()
    {
        return controlledPackage;
    }

    /**
     * sets the package control flag
     * @param value
     */
    public void setControlledPackage(boolean value)
    {
        controlledPackage = value;
    }

    /**
     * renames the script
     * @param name
     */
    public void rename(String name) {
        this.fullName = getPackage() + "." + name;
    }

    // </editor-fold>
}
